package com.demo.seckill.common.dynamicquery;

import java.util.List;

import javax.persistence.EntityManager;
import javax.persistence.PersistenceContext;
import javax.persistence.Query;

import org.hibernate.SQLQuery;
import org.hibernate.transform.Transformers;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.stereotype.Repository;

/**
 * @author libo
 * @ClassName DynamicQueryImpl
 * @Description: spring-jpa调用接口
 * @date 2018/11/30 16:45
 */
@Repository
public class DynamicQueryImpl implements DynamicQuery {
    Logger logger = LoggerFactory.getLogger(DynamicQueryImpl.class);

    @PersistenceContext
    private EntityManager entityManager;

    public EntityManager getEntityManager(){
        return entityManager;
    }
    @Override
    public void save(Object entity) {
        entityManager.persist(entity);
    }
    @Override
    public void update(Object entity) {
        entityManager.merge(entity);
    }
    @Override
    public <T> void delete(Class<T> entityClass, Object entiryId) {
        delete(entityClass,new Object[]{entiryId});
    }
    @Override
    public <T> void delete(Class<T> entityClass, Object[] entityids) {
       for (Object e : entityids){
           entityManager.remove(e);
       }
    }
    @Override
    public <T> List<T> nativeQueryList(String nativeSql, Object... params) {
        Query q = createNativeQuery(nativeSql,params);
        q.unwrap(SQLQuery.class).setResultTransformer(Transformers.TO_LIST);
        return q.getResultList();
    }

    @Override
    public <T> List<T> nativeQueryListMap(String nativeSql, Object... params) {
        Query q = createNativeQuery(nativeSql, params);
        q.unwrap(SQLQuery.class).setResultTransformer(Transformers.ALIAS_TO_ENTITY_MAP);
        return q.getResultList();
    }

    @Override
    public <T> List<T> nativeQueryListModel(Class<T> resultClass, String nativeSql, Object... params) {
        Query q = createNativeQuery(nativeSql,params);
        q.unwrap(SQLQuery.class).setResultTransformer(Transformers.aliasToBean(resultClass));
        return  q.getResultList();
    }

    @Override
    public Object nativeQueryObject(String nativeSql, Object... params) {
        return  createNativeQuery(nativeSql,params).getSingleResult();
    }

    @Override
    public Object nativeQueryArray(String nativeSql, Object... params) {
        return (Object)createNativeQuery(nativeSql, params).getSingleResult();
    }

    @Override
    public int nativeExecuteUpdate(String nativeSql, Object... params) {
        return createNativeQuery(nativeSql, params).executeUpdate();
    }

    private Query createNativeQuery(String sql, Object... params){
        Query q = entityManager.createNativeQuery(sql);
        if(params !=null && params.length > 0){
            for (int i=0;i<params.length;i++){
                q.setParameter(i+1,params[i]);
            }
        }
        return q;
    }
}
